package service

import (
	"api-gateway-center/config"
	"api-gateway-center/domain/loadBanlance/model"
	"bytes"
	"errors"
	"fmt"
	"log"
	"os"
	"os/exec"
	"path/filepath"
)

type LoadBalancingService struct {
}

func (this *LoadBalancingService) UpdateNginxConfig(config *model.NginxConfig) error {
	//创建nginx文件
	err := createNginxConfig(config)
	if err == nil {
		log.Println("创建 Nginx 配置文件完成")
	}
	//刷新nginx
	err = refreshNginxConfig()
	if err == nil {
		log.Println("Nginx 重启完成")
	}
	return err
}
func createNginxConfig(nginxConfig *model.NginxConfig) error {
	//1.创建文件内容
	nginxConfigContentStr := buildNginxConfig(nginxConfig.UpstreamList, nginxConfig.LocationList)
	//2.文件路径
	filePath := config.FilePath
	log.Println("文件名字为" + filePath) //前后两次filePath不一样 第二次 D:\Data\nginxnginx.conf
	//3.检查文件是否存在  PS:os.IsNotExist(err)大坑
	if _, err := os.Stat(filePath); errors.Is(err, os.ErrNotExist) {
		//3.1文件不存在，创建文件
		_, err := os.Create(filePath)
		if err != nil {
			log.Fatalf("Failed to create file: %v", err)
			return err
		}
		log.Printf("nginx.conf file created successfully.")
	}
	// 写入内容
	if err := os.WriteFile(filePath, []byte(nginxConfigContentStr), os.ModePerm); err != nil {
		log.Fatalf("Failed to write to file: %v", err)
		return err
	}
	// 返回
	return nil
}
func refreshNginxConfig() error {
	// 获取当前工作目录
	currentDir, err := os.Getwd()
	if err != nil {
		fmt.Println("Error getting current directory:", err)
		return err
	}
	path := filepath.Join(config.FilePath, "..")
	path = filepath.Join(path, "..")
	defer os.Chdir(currentDir)
	if err := os.Chdir(path); err != nil {
		return errors.New("进入" + path + "失败:" + err.Error())
	}
	if err := exec.Command(".\\nginx", "-s", "reload").Err; err != nil {
		return errors.New("nginx未打开或" + err.Error())
	}
	return nil
}

// 写nginx文件
func buildNginxConfig(upstreamList []*model.UpstreamVo, locationList []*model.LocationVo) string {
	var buf bytes.Buffer

	// Nginx基础配置
	buf.WriteString(`
#user  nobody;
worker_processes  1;

#error_log  logs/error.log;
#error_log  logs/error.log  notice;
#error_log  logs/error.log  info;

#pid        logs/nginx.pid;

events {
     worker_connections   1024;
}

http {
     include       mime.types;
    default_type  application/octet-stream;

     log_format  main  '$remote_addr - $remote_user [$time_local] "$request" '
                      '$status $body_bytes_sent "$http_referer" '
                      '"$http_user_agent" "$http_x_forwarded_for"';

     access_log  logs/access.log  main;

     sendfile         on;
     #tcp_nopush      on;

     keepalive_timeout   65;

     #gzip   on;

     # 设定负载均衡的服务器列表
`)
	// 组装配置 Upstream
	for _, upstream := range upstreamList {
		buf.WriteString(fmt.Sprintf("\tupstream %s {\n", upstream.Name))
		buf.WriteString(fmt.Sprintf("\t\t%s\n", upstream.Strategy))
		for _, server := range upstream.Servers {
			buf.WriteString(fmt.Sprintf("\t\tserver %s;\n", server))
		}
		buf.WriteString("\t}\n\n")
	}
	// 替换配置
	buf.WriteString(`
     # HTTP服务器
     server {
         # 监听80端口，用于HTTP协议
         listen   80;

         # 定义使用IP/域名访问
         server_name `)
	buf.WriteString(config.Nginx_server_name)
	buf.WriteString(`;

         # 首页
         index index.html;

         # 反向代理的路径（upstream绑定），location 后面设置映射的路径
         # location / {
         #     proxy_pass http://127.0.0.1:9090;
         # }
`)
	// 组装配置 Location
	for _, location := range locationList {
		buf.WriteString(fmt.Sprintf("\t\t\tlocation %s {\n", location.Name))
		buf.WriteString(fmt.Sprintf("\t\t\trewrite ^%s(.*)$ /$1 break;\n", location.Name))
		buf.WriteString(fmt.Sprintf("\t\t\tproxy_pass %s\n", location.Proxy_pass))
		buf.WriteString("\t\t}\n\n")
	}
	// 替换配置
	buf.WriteString("     }\n") // 这里是server块的结束

	buf.WriteString("}\n") // 这里是http块的结束

	return buf.String()
}
